﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.SharePoint.Administration;

namespace Umbrella.Whs.SharePoint.WebConfigModifications
{
    internal abstract class WebConfigModification
    {
        protected readonly log4net.ILog _log;

        public abstract string Id
        {
            get;
        }

        public string Owner
        {
            get { return ("CodenameUmbrella-" + this.Id); }
        }

        protected abstract IEnumerable<SPWebConfigModification> CreateInternal();

        public void AddModification(ICollection<SPWebConfigModification> mods)
        {
            if (mods == null)
                throw new ArgumentNullException("mods");

            try
            {
                // create the modifications internally
                var src = CreateInternal();

                if (src == null)
                    throw new NotImplementedException("CreateInternal() returned null");

                // add them to the collection
                var owner = this.Owner;
                var order = 100u;

                foreach (var m in src)
                {
                    // ensure owner and order
                    m.Owner = owner;
                    m.Sequence = (++order);

                    // continue adding
                    mods.Add(m);
                }
            }
            catch (Exception x)
            {
                _log.Error("Failed to add web config modification: " + this.Id, x);

                throw;
            }
        }

        public void RemoveModification(ICollection<SPWebConfigModification> mods)
        {
            if (mods == null)
                throw new ArgumentNullException("mods");

            try
            {
                // gather all modification belonging to
                // this modification
                var rm = (from m in mods where m.Owner == this.Owner select m);

                // remove the modifications
                foreach (var m in rm)
                    mods.Remove(m);
            }
            catch (Exception x)
            {
                _log.Error("Failed to remove web config modification: " + this.Id, x);

                throw;
            }
        }

        protected WebConfigModification()
        {
            _log = log4net.LogManager.GetLogger(GetType());
        }
    }
}
